
#include "stdafx.h"
#include "NowDisplay.h"
#include "DPIForm.h"
#include "FontFactory.h"

IMPLEMENT_DYNAMIC(CNowDisplay, CTimeDisplay)

CNowDisplay::CNowDisplay()
{
	m_fFactory = new CFontFactory();
	m_fFactory->Create(_T("Arial"), 80, 26, FW_BOLD)->SetMark(FM_TimeNum)
		->Create(_T("Arial"), 60, 20, FW_BOLD)->SetMark(FM_TimeMs);
	HDC hScrDC = CreateScrDC();
	CSize szTime, szMs;
	HFONT oldFont = (HFONT)::SelectObject(hNumMemDC, m_fFactory->GetMark(FM_TimeNum));
	for (int i = 0; i < 12; i++)
	{
		if (i < 10) swprintf_s(nmTime[i].v, L"%d", i); else wcscpy_s(nmTime[i].v, i == 10 ? L":" : L".");
		::GetTextExtentPoint32(hNumMemDC, nmTime[i].v, 1, &nmTime[i].sz);
		if (i < 10) nmTime[i].getSize(i, szTime);
	}
	::SelectObject(hNumMemDC, m_fFactory->GetMark(FM_TimeMs));
	for (intptr_t i = 0; i < 10; i++)
	{
		wcscpy_s(nmMs[i].v, nmTime[i].v);
		::GetTextExtentPoint32(hNumMemDC, nmMs[i].v, 1, &nmMs[i].sz);
		nmMs[i].getSize(i, szMs);
	}
	::SelectObject(hNumMemDC, oldFont);
	for (intptr_t i = 0; i < 12; i++)
	{
		if (i < 10)
		{
			nmTimePos[i] = CPoint((szTime.cx - nmTime[i].sz.cx) >> 1, (szTime.cy - nmTime[i].sz.cy) >> 1);
			CreateNum(hScrDC, &nmTime[i], szTime);
			nmMsPos[i] = CPoint((szMs.cx - nmMs[i].sz.cx) >> 1, (szMs.cy - nmMs[i].sz.cy) >> 1);
			CreateNum(hScrDC, &nmMs[i], szMs);
		}
		else
		{
			nmTimePos[i] = CPoint(0, 0);
			CreateNum(hScrDC, &nmTime[i], nmTime[i].sz);
		}
	}
	for (intptr_t i = 0, x = CDPIForm::DPIX(12), y = 0; i < 10; i++)		//00:00:00.x
	{
		numRect[i].left = (int)x;
		if (i == 2 || i == 5)
		{
			x += nmTime[10].sz.cx; numIndex[i] = 10;
			numRect[i].top = (int)(y + ((szTime.cy - nmTime[10].sz.cy) >> 1));
			numRect[i].bottom = numRect[i].top + nmTime[10].sz.cy;
		}
		else if (i == 8)
		{
			x += nmTime[11].sz.cx; numIndex[i] = 11;
			numRect[i].top = (int)(y + ((szTime.cy - nmTime[11].sz.cy) >> 1));
			numRect[i].bottom = numRect[i].top + nmTime[11].sz.cy;
		}
		else if (i == 9)
		{
			x += szMs.cx; numIndex[i] = -1;
			numRect[i].top = (int)(y + szTime.cy - szMs.cy - CDPIForm::DPIY(4));
			numRect[i].bottom = numRect[i].top + szMs.cy;
		}
		else
		{
			x += szTime.cx; numIndex[i] = -1;
			numRect[i].top = (int)y;
			numRect[i].bottom = numRect[i].top + szTime.cy;
		}
		numRect[i].right = (int)x;
	}
	CreateMemBitmap(hScrDC, numRect[9].right + CDPIForm::DPIX(12), numRect[9].bottom);
	::DeleteDC(hScrDC);
	time.Set(-1, -1, -1); clrText = RGB(0, 0, 0);
}

CNowDisplay::~CNowDisplay()
{
	for (intptr_t i = 0; i < 12; i++)
	{
		if (nmTime[i].bmp) ::DeleteObject(nmTime[i].bmp);
		if (i < 10 && nmMs[i].bmp) ::DeleteObject(nmMs[i].bmp);
	}
	delete m_fFactory;
}


BEGIN_MESSAGE_MAP(CNowDisplay, CTimeDisplay)
END_MESSAGE_MAP()

void CNowDisplay::setTextColor(COLORREF clr)
{
	if (clrText == clr) return;
	clrText = clr; ::SetTextColor(hNumMemDC, clrText);
	HFONT oldFont = (HFONT)::SelectObject(hNumMemDC, m_fFactory->GetMark(FM_TimeNum));
	for (intptr_t i = 0; i < 12; i++)
	{
		HBITMAP hold = (HBITMAP)::SelectObject(hNumMemDC, nmTime[i].bmp);
		::TextOut(hNumMemDC, nmTimePos[i].x, nmTimePos[i].y, nmTime[i].v, 1);
		::SelectObject(hNumMemDC, hold);
	}
	::SelectObject(hNumMemDC, m_fFactory->GetMark(FM_TimeMs));
	for (intptr_t i = 0; i < 10; i++)
	{
		HBITMAP hold = (HBITMAP)::SelectObject(hNumMemDC, nmMs[i].bmp);
		::TextOut(hNumMemDC, nmMsPos[i].x, nmMsPos[i].y, nmMs[i].v, 1);
		::SelectObject(hNumMemDC, hold);
	}
	::SelectObject(hNumMemDC, oldFont);
	for (intptr_t i = 0; i < 10; i++) drawOut(i, numIndex[i]);
}

bool CNowDisplay::setTime(int h, int m, int s, int ms)
{
	displayChanged = false;
	if (time.hour != h)
	{
		time.hour = h;
		intptr_t v = (intptr_t)(time.hour / 10) & 0xf; if (v != numIndex[0]) drawOut(0, v);
		v = time.hour % 10; if (v != numIndex[1]) drawOut(1, v);
	}
	if (time.minute != m)
	{
		time.minute = m;
		intptr_t v = (intptr_t)(time.minute / 10) & 0xf; if (v != numIndex[3]) drawOut(3, v);
		v = time.minute % 10; if (v != numIndex[4]) drawOut(4, v);
	}
	if (time.second != s)
	{
		time.second = s;
		intptr_t v = (intptr_t)(time.second / 10) & 0xf; if (v != numIndex[6]) drawOut(6, v);
		v = time.second % 10; if (v != numIndex[7]) drawOut(7, v);
	}
	intptr_t v = (intptr_t)(ms / 100) & 0xf; if (v != numIndex[9]) drawOutMs(v);
	return displayChanged;
}

void CNowDisplay::drawOut(intptr_t id, intptr_t n)
{
	numIndex[id] = n;
	if (n >= 0 && n < 12)
	{
		CTimeDisplay::drawOut(numRect[id], nmTime[n].bmp); displayChanged = true;
	}
}
void CNowDisplay::drawOutMs(intptr_t n)
{
	numIndex[9] = n;
	if (n >= 0 && n < 10)
	{
		CTimeDisplay::drawOut(numRect[9], nmMs[n].bmp); displayChanged = true;
	}
}
